﻿using System;
using System.Collections.Generic;
using System.Text;

namespace NetworkCrashSimulator.Core
{
    public class TimedCrash
    {
        /// <summary>
        /// Name of the network adapter that will be crashed.
        /// </summary>
        private string AdapterName { get; set; }

        /// <summary>
        /// Timer to the network adapter crash.
        /// </summary>
        public System.Timers.Timer CrashTimer { get; private set; }

        /// <summary>
        /// Timer to the network adapter repair.
        /// </summary>
        public System.Timers.Timer RepairTimer { get; private set; }

        /// <summary>
        /// The date and time when the crashing will be over.
        /// </summary>
        private DateTime EndDateTime { get; set; }

        /// <summary>
        /// Whow many craches.
        /// </summary>
        private int Crashes { get; set; }

        /// <summary>
        /// How much time to recover from each crash.
        /// </summary>
        private int TimeToRecover { get; set; }

        /// <summary>
        /// Whow many miliseconds for each crash.
        /// </summary>
        private int CrashEvery { get; set; }

        /// <summary>
        /// Constructor.
        /// </summary>
        public TimedCrash()
        {
            CrashTimer = new System.Timers.Timer();
            CrashTimer.AutoReset = true;
            CrashTimer.Elapsed += new System.Timers.ElapsedEventHandler(CrashTick);

            RepairTimer = new System.Timers.Timer();
            RepairTimer.AutoReset = true;
            RepairTimer.Elapsed += new System.Timers.ElapsedEventHandler(RepairTick);
        }

        /// <summary>
        /// Event raised by CrashTimer.Elapsed
        /// </summary>
        private void CrashTick(object sender, System.EventArgs e)
        {
            if (DateTime.Now <= EndDateTime)
            {
                Actions.CrashAdapter(AdapterName);
                RepairTimer.Start();
            }
            else
            {
                Actions.GenerateConsoleLine(string.Empty, false);
                Actions.GenerateConsoleLine("The crashes has stopped.");
                CrashTimer.Stop();
            }
        }

        /// <summary>
        /// Event raised by RepairTimer.Elapsed
        /// </summary>
        private void RepairTick(object sender, System.EventArgs e)
        {
            Actions.RepairAdapter(AdapterName);
            RepairTimer.Stop();
        }

        /// <summary>
        /// Start the timmed network adapter crashing.
        /// </summary>
        /// <param name="adapterName">Name of the adapter that will be crashed.</param>
        /// <param name="totalTime">Total duration time. (Minutes)</param>
        /// <param name="crashes">Whow many craches.</param>
        /// <param name="timeToRecover">Time to recover from each crash. (Seconds)</param>
        public void Execute(string adapterName, int totalTime, int crashes, int timeToRecover)
        {
            AdapterName = adapterName;
            totalTime = totalTime * 60000;
            EndDateTime = DateTime.Now.AddMilliseconds(totalTime);
            Crashes = crashes;
            TimeToRecover = timeToRecover * 1000;

            CrashEvery = totalTime / Crashes;

            CrashTimer.Interval = CrashEvery - 10;

            RepairTimer.Interval = TimeToRecover;

            Actions.GenerateConsoleLine(string.Empty, false);
            Actions.GenerateConsoleLine("Starting timed crashes...");

            CrashTimer.Start();

            while (CrashTimer.Enabled || RepairTimer.Enabled) ;
        }
    }
}
